/**
 * representation of Lager
 * @author Lukas Koell
 * @author Johannes Riedmann
 * @author David Medenjak
 */

public class Lager {

    /** size of the lager */
    protected int size;
    /** current units stored in this Lager */
    protected Integer storage;
    /** name of the Lager */
    protected String name;
    /** consumer currently using the Lager */    
    private Konsument consumer;

    public Lager(int size) {
        this.size = size;
        this.storage = 0;
        consumer = null;
    }

    /**
     * names or renames the lager by params value
     * @param name name the lager should have
     */
    public void setName(String name) {
        this.name = name;
    }

    /**
     * inserts a certain amount of a resource to the storage
     * @param amount number of units inserted
     * @return true if enough space is available, false if not
     */
    public synchronized int insert(int amount) {
        if (storage + amount <= size) {
            storage += amount;
            notify();
//            System.out.println(amount + "/" + amount + " inserted into " + name + " (" + storage + ")");
            return amount;
        } else {
            int tmp = storage;
            storage = size;
            notify();
//            System.out.println(size - tmp + "/" + amount + " inserted into " + name + " (" + storage + ")");
            return size - tmp;
        }
    }

    /**
     * worker takes out a certain amout of units from the storage
     * @param amount number of units taken out
     * @param consumer current consumer working on the Lager
     * @return 0 if consumer doesn't match conditions, else returns amount
     */
    public synchronized int takeOut(int amount, Konsument consumer) {
        if (this.consumer != null && this.consumer != consumer) {
            notify();
            return 0;
        }
        if (storage - amount >= 0) {
            storage -= amount;
            notify();
//            System.out.println(amount + "/" + amount + " taken of " + name + " (" + storage + ")");
            return amount;
        } else {
            int tmp = storage;
            storage = 0;
            notify();
//            System.out.println(tmp + " taken of " + name + " (" + storage + ")");
            return tmp;
        }
    }

    /**
     * @return true if storage is not full, else false
     */
    public boolean canInsert() {
        if (storage < size) {
            notifyAll();
            return true;
        }
        return false;
    }

    /**
     * @return true if storage has units available, else false
     */
    public boolean canTakeOut() {
        if (storage > 0) {
            notifyAll();
            return true;
        }
        return false;
    }

    /**
     * @return current units in the storage
     */
    public int getStorage() {
        return storage;
    }

    /**
     * sets a new customer for the Lager
     * @param consumer current customer
     * @param newConsumer new customer
     */
    public synchronized void setConsumer(Konsument consumer, Konsument newConsumer) {
        if (this.consumer == null) {
            this.consumer = newConsumer;
        } else {
            if (this.consumer == consumer) {
                this.consumer = newConsumer;
            } else {
                return;
            }
        }
    }
}
